﻿﻿using System;
 using System.Collections;
 using System.Collections.Generic;
 using Com.Enemy.EnemySystem.EnemyLifecycle;
using Com.Enemy.EnemySystem.Tools;
using Pathfinding;
 using Script.EnemySystem.EnemyState;
 using Script.EnemySystem.Tools;
using UnityEngine;

namespace Com.Enemy.EnemySystem.EnemyAI
{
    /// <summary>
    ///  自动寻路AI
    /// </summary>
    public class EnemyStateBase : MonoBehaviour
    {
        
        protected Animator animator;
        
        protected EnemyBody Body;
        
        protected Rigidbody2D Rb;

        protected EnemyAnimTime animTime;

        protected IEnumerator coroutine;

        public EnemyAnimTime AnimTime => animTime;

        protected virtual void Awake()
        {
            Body = GetComponent<EnemyBody>();
            animator = GetComponent<Animator>();
            animTime = new EnemyAnimTime();
        }

        protected virtual void Start()
        {
        }

        protected virtual void GetIntoState(EnemyState state)
        {
            if(state == Body.Data.State)
                return;
            
            if (Body.Data.State != EnemyState.Idle)
            {
                animator.SetBool(Body.Data.State.ToString(), false);
                // StopCoroutine(coroutine);
            }
            animator.SetBool(state.ToString(), true);
            Body.Data.State = state;
        }
        protected virtual void ExitState()
        {
            if (Body.Data.State >= EnemyState.Avoid)
            {
                Body.CoolDownSystem.AddColdDownInfo(Body.Data.State, Body.Data.StateColdDown[(int) Body.Data.State]);
            }

            if (Body.Data.State != EnemyState.Idle)
            {
                animator.SetBool(Body.Data.State.ToString(), false);
            }

            Body.Data.State = EnemyState.Idle;
            
        }

        protected IEnumerator PlayStateOnCoroutine(EnemyState state)
        {
            GetIntoState(state);
            if(state == EnemyState.Walk)
                yield break;
            
            yield return new WaitForSeconds(animTime.GetStateTime(state));
            
            ExitState();
        }

        public virtual void PlayState(EnemyState state)
        {
            coroutine = PlayStateOnCoroutine(state);
            StartCoroutine(coroutine);
        }

        public virtual void TakeDamage(int playerId, float damage, float knockback)
        {
            
        }
        
        protected virtual IEnumerator TakeDamageTask(int playerId, BaseData damage, float knockback)
        {
            GetIntoState(EnemyState.Hurt);
            Body.TakeDamage(playerId ,damage, knockback);
            yield return new WaitForSeconds(.1f);
            ExitState(EnemyState.Hurt);
        }

        protected virtual void ExitStateTo(EnemyState state)
        {
            if(Body.Data.State > EnemyState.Hurt)
                Body.CoolDownSystem.AddColdDownInfo(Body.Data.State, Body.Data.StateColdDown[(int) Body.Data.State]);
            animator.SetBool(Body.Data.State.ToString(), false);
            Body.Data.State = state;
        }
        
        protected virtual void ExitState(EnemyState state)
        {
            if(Body.Data.State > EnemyState.Hurt)
                Body.CoolDownSystem.AddColdDownInfo(state, Body.Data.StateColdDown[(int) state]);
            animator.SetBool(state.ToString(), false);
            Body.Data.State = EnemyState.Idle;
        }

        private static readonly int Hurt = Animator.StringToHash("Hurt");
        protected virtual void HurtTrigger()
        {
            animator.SetTrigger(Hurt);
            Body.Data.State = EnemyState.Hurt;
        }

    }
}